using System;
using System.IO;
using System.IO.Compression;
using System.Security.Cryptography;

namespace MEA.Misc
{
	public class CryptedCompression
	{
		private byte[] key;

		private readonly byte[] IV = new byte[16]
		{
			16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
			10, 11, 12, 13, 14, 15
		};

		public int EncryptStream(MemoryStream inputStream, string passphrase, byte[] i_workBuffer_ab)
		{
			try
			{
				int num = 0;
				MemoryStream memoryStream = new MemoryStream(i_workBuffer_ab, 0, i_workBuffer_ab.Length, true, true);
				memoryStream.SetLength(0L);
				i_workBuffer_ab.Initialize();
				Rijndael rijndael = Rijndael.Create();
				rijndael.Padding = PaddingMode.PKCS7;
				if (inputStream != null && inputStream.Length > 0)
				{
					inputStream.Position = 0L;
				}
				GenerateKey(passphrase);
				CryptoStream cryptoStream = new CryptoStream(memoryStream, rijndael.CreateEncryptor(key, IV), CryptoStreamMode.Write);
				try
				{
					for (int num2 = inputStream.ReadByte(); num2 != -1; num2 = inputStream.ReadByte())
					{
						cryptoStream.WriteByte((byte)num2);
					}
				}
				catch (Exception)
				{
				}
				finally
				{
					cryptoStream.FlushFinalBlock();
					num = (int)memoryStream.Length;
					cryptoStream.Close();
				}
				return num;
			}
			catch (CryptographicException ex2)
			{
				Console.WriteLine("A Cryptographic error occurred: {0}", ex2.Message);
			}
			catch (UnauthorizedAccessException ex3)
			{
				Console.WriteLine("A file error occurred: {0}", ex3.Message);
			}
			return -1;
		}

		public MemoryStream DecryptStream(MemoryStream inputStream, string passphrase, byte[] i_workingBuffer_ab)
		{
			try
			{
				MemoryStream memoryStream = new MemoryStream(i_workingBuffer_ab, 0, i_workingBuffer_ab.Length, true, true);
				memoryStream.SetLength(0L);
				Rijndael rijndael = Rijndael.Create();
				rijndael.Padding = PaddingMode.PKCS7;
				if (inputStream != null && inputStream.Length > 0)
				{
					inputStream.Position = 0L;
				}
				GenerateKey(passphrase);
				CryptoStream cryptoStream = new CryptoStream(inputStream, rijndael.CreateDecryptor(key, IV), CryptoStreamMode.Read);
				try
				{
					for (int num = cryptoStream.ReadByte(); num != -1; num = cryptoStream.ReadByte())
					{
						memoryStream.WriteByte((byte)num);
					}
				}
				catch (Exception)
				{
				}
				finally
				{
					inputStream.Close();
				}
				return memoryStream;
			}
			catch (CryptographicException)
			{
				return null;
			}
			catch (UnauthorizedAccessException)
			{
				return null;
			}
			catch (Exception)
			{
				return null;
			}
		}

		private void GenerateKey(string pw)
		{
			PasswordDeriveBytes passwordDeriveBytes = new PasswordDeriveBytes(pw, new byte[13]
			{
				16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
				10, 11, 12
			});
			key = passwordDeriveBytes.GetBytes(24);
		}

		public int GZipDecompress(MemoryStream inputStream, byte[] i_workBuffer_ab)
		{
			MemoryStream memoryStream = new MemoryStream(i_workBuffer_ab, 0, i_workBuffer_ab.Length, true, true);
			memoryStream.SetLength(0L);
			try
			{
				inputStream.Position = 0L;
				GZipStream gZipStream = new GZipStream(inputStream, CompressionMode.Decompress);
				int num = gZipStream.ReadByte();
				int num2 = 0;
				while (num != -1)
				{
					memoryStream.WriteByte((byte)num);
					num = gZipStream.ReadByte();
					num2++;
				}
				memoryStream.Flush();
				gZipStream.Close();
				return (int)memoryStream.Position;
			}
			catch (InvalidDataException)
			{
			}
			catch (IndexOutOfRangeException)
			{
			}
			finally
			{
				inputStream.Close();
			}
			return -1;
		}

		public MemoryStream GZipCompress(MemoryStream inputStream, byte[] i_workBuffer_ab)
		{
			i_workBuffer_ab.Initialize();
			MemoryStream memoryStream = null;
			try
			{
				memoryStream = new MemoryStream(i_workBuffer_ab, 0, i_workBuffer_ab.Length, true, true);
				memoryStream.SetLength(0L);
				GZipStream gZipStream = new GZipStream(memoryStream, CompressionMode.Compress, true);
				gZipStream.Write(inputStream.GetBuffer(), 0, (int)inputStream.Length);
				gZipStream.Flush();
				gZipStream.Close();
			}
			catch (InvalidDataException)
			{
			}
			catch (IndexOutOfRangeException)
			{
			}
			if (inputStream != null)
			{
				try
				{
					inputStream.Close();
				}
				catch
				{
				}
			}
			return memoryStream;
		}
	}
}
